import { Shape } from '@antv/x6'
import config, { portAttrs } from '../config'

export class CustomLine extends Shape.Path {
  getAllPortsIds() {
    return this.getPortsByGroup('outIn').map((item) => item.id)
  }

  getUsedPortsIds(graph) {
    const outgoingEdges = graph.getConnectedEdges(this) || []
    const allPortIds = []
    const portsIds = this.getAllPortsIds()
    outgoingEdges.forEach((edge) => {
      allPortIds.push(edge.getSourcePortId())
      allPortIds.push(edge.getTargetPortId())
    })
    return portsIds.filter((id) => allPortIds.includes(id))
  }

  getNewInPorts(length) {
    return Array.from(
      {
        length
      },
      () => {
        return {
          group: 'outIn'
        }
      }
    )
  }

  updateOutPorts(graph) {
    const minNumberOfPorts = 1
    const ports = this.getAllPortsIds()
    const usedPorts = this.getUsedPortsIds(graph)
    const newPorts = this.getNewInPorts(Math.max(minNumberOfPorts - usedPorts.length, 1))
    if (ports.length === usedPorts.length) {
      this.addPorts(newPorts)
    } else if (ports.length > usedPorts.length + 1) {
      const portId = ports.find((id) => !usedPorts.includes(id))
      this.removePort(portId)
    }

    return this
  }
}

CustomLine.config({
  constructorName: 'custom-line',
  width: 80,
  attrs: {
    root: {
      magnet: false
    },
    body: {
      fill: config.nodeBgColor,
      stroke: config.nodeStroke,
      strokeWidth: 3
    },
    data: {
      width: config.nodeWidth,
      height: 3,
      angle: config.nodeAngle,
      showHeight: false,
      showText: false
    }
  },
  path: 'M0,15 80,15 Z',
  ports: {
    items: [
      {
        group: 'outIn'
      }
    ],
    groups: {
      outIn: {
        position: {
          name: 'top'
        },
        attrs: {
          portBody: {
            magnet: true,
            r: 4,
            stroke: config.nodeStroke,
            strokeWidth: config.nodeStrokeWidth,
            fill: '#fff',
            style: {
              visibility: 'hidden'
            }
          }
        }
      },
      right: {
        position: 'right',
        attrs: portAttrs
      },
      left: {
        position: 'left',
        attrs: portAttrs
      }
    }
  },
  portMarkup: [
    {
      tagName: 'circle',
      selector: 'portBody'
    }
  ]
})
